package jp.sourceforge.akjrcp.text_douga.video;

import java.awt.Graphics2D;
import java.awt.image.BufferedImage;
import java.io.File;
import java.io.IOException;

import javax.imageio.ImageIO;

import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;

import jp.sourceforge.akjrcp.ffmpeg.JpegPipeWriter;
import jp.sourceforge.akjrcp.text_douga.DougaPreference;
import jp.sourceforge.akjrcp.text_douga.EffectData;
import jp.sourceforge.akjrcp.text_douga.ImageObject;
import jp.sourceforge.akjrcp.text_douga.ItemData;
import jp.sourceforge.akjrcp.text_douga.VideoData;
import jp.sourceforge.akjrcp.text_douga.parser.SimpleParser;
import jp.sourceforge.akjrcp.util.image.ImageUtils;

public class PipedVideoWriter extends AbstractVideoWriter{
	public static Log log = LogFactory.getLog(PipedVideoWriter.class);

private JpegPipeWriter jpegPipeWriter;
private ItemData[] itemDatas;
private EffectData[] effectDatas;


private DougaPreference dougaPreference;


private BufferedImage lastImage;
private VideoData lastVideoData;

private BufferedImage bufferedImage;
private Graphics2D graphics2D;

/**
 * 
 * @param dougaPreference
 * @param jpegPipeWriter
 * @param workingDir 作業用フォルダー
 */
public PipedVideoWriter(DougaPreference dougaPreference,JpegPipeWriter jpegPipeWriter,File workingDir){
	this.dougaPreference=dougaPreference;
	this.jpegPipeWriter=jpegPipeWriter;
	setWorkingDir(workingDir);
}

public EffectData[] getEffectDatas() {
	return effectDatas;
}

public void setEffectDatas(EffectData[] effectDatas) {
	this.effectDatas = effectDatas;
}

public ItemData[] getItemDatas() {
	return itemDatas;
}

/**
 * set must sorted items
 * @param itemDatas
 */
public void setItemDatas(ItemData[] itemDatas) {
	this.itemDatas = itemDatas;
}

public JpegPipeWriter getJpegPipeWriter() {
	return jpegPipeWriter;
}

public void setJpegPipeWriter(JpegPipeWriter jpegPipeWriter) {
	this.jpegPipeWriter = jpegPipeWriter;
}

public BufferedImage getLastImage(){
	return lastImage;
}
public boolean writeFrame(VideoData videoData, BufferedImage image) throws IOException {
	//log.trace("writeframe:"+writed);
	if(bufferedImage==null){
		bufferedImage=new BufferedImage(image.getWidth(),image.getHeight(),BufferedImage.TYPE_INT_RGB);//alpha cant write as jpeg
		graphics2D=(Graphics2D) bufferedImage.getGraphics();
	}
	/*
	 * save any videoData's first frame and last frame! 
	 * 最初と最後のフレーム画像を保存します。これはエフェクト処理で必要になります。
		this is for effect.
		warrning
		end frame can set only next video Frame called.
	 */
	if(videoData!=lastVideoData){
		//first frame
		File outFrame=getWorkingFrameFile(writed+1);
		ImageUtils.writeJpegWithQuality(image, outFrame, 1.0f);
		
		//last frame of last videoData
		if(lastImage!=null){
			//log.warn("write:last one"+writed);
			ImageUtils.writeJpegWithQuality(lastImage, getWorkingFrameFile(writed), 1.0f);
			/*
			 //for debug
			 if(lastVideoData instanceof EffectableVideoData){
				EffectableVideoData v=(EffectableVideoData)lastVideoData;
				//log.trace(v.getStartEffect());
				//log.trace(v.getEndEffect());
			}*/
		}
	}
	
	graphics2D.drawImage(image,null,0,0);
	
	effectAndItem(bufferedImage,writed+1);
	if(jpegPipeWriter==null){
		log.warn("jpegPipeWriter null");
		throw new IOException("jpegPipeWriter null");
	}
	jpegPipeWriter.writeJpeg(bufferedImage);
	
	
	
	
	
	writed++;
	//System.out.println("writed:"+writed);
	lastImage=bufferedImage;
	lastVideoData=videoData;
	
	if(writed==maxFrame){
		return true;
	}else{
		return false;
	}
	
	

}

private void effectAndItem(BufferedImage img,int index){
	ImageObject imageObject= new ImageObject(img);
	
	
	
	if(itemDatas!=null){
	for (int k = 0; k < itemDatas.length; k++) {
		
		try {
			boolean writed=itemDatas[k].writeFrame(dougaPreference,imageObject,
					index);
			
			
		} catch (IOException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
		}
	}
	
	
	
	if(effectDatas!=null){
		for (int k = 0; k < effectDatas.length; k++) {
			effectDatas[k].setExportDir(getWorkingDir());
			try {
				boolean writed=effectDatas[k].writeFrame(dougaPreference, imageObject,
						index);
			} catch (IOException e) {
				// TODO Auto-generated catch block
				e.printStackTrace();
			}
			}
		}
	
}



public void close() throws IOException{
	jpegPipeWriter.close();
}

}
